package cn.com.generaldata.os.importer;

import java.io.File;
import java.io.FileFilter;
import java.io.FileNotFoundException;
import java.util.ArrayList;
import java.util.List;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;

import cn.com.generaldata.os.pojo.mvc.Report;
import cn.com.generaldata.os.report.xml.ReportImporter;

public class Importer {

	private static Log log = LogFactory.getLog(Importer.class);
	private static final String HEADER = "[OS][Importer]";

	public static List<Report> importReports(String importRootPath, String backupRootPath) throws FileNotFoundException {

		List<Report> reports = new ArrayList<Report>();

		File fileImportRoot = getPath(importRootPath);
		File fileBackupRoot = getPath(backupRootPath);

		checkSamePath(fileImportRoot, fileBackupRoot);

		// File[] dirImports = getChildDirs(fileImportRoot);
		File[] dirImports = fileImportRoot.listFiles();

		// for (File file : dirImports) {
		// String backupChildPath = backupRootPath + "/" + file.getName() + "/";
		//
		// // File[] xmls = getReportFiles(file);
		// File[] xmls = file.listFiles();
		// for (File xmlFile : xmls) {
		// if (checkBackupPath(xmlFile, backupChildPath)) {
		// reports.add(ReportImporter.importReport(xmlFile.getAbsolutePath()));
		// log.debug(HEADER + "[importReports]Import successful, file name is " + xmlFile.getAbsolutePath() + ".");
		//
		// backupFile(xmlFile, backupChildPath);
		// log.debug(HEADER + "[importReports]Backup succeful, file name is " + backupChildPath + "/bak_" +
		// xmlFile.getName());
		// }
		// //deleteDir(file);
		// }
		// }
		for (File dirImport : dirImports) {
			reports.add(ReportImporter.importReport(dirImport.getAbsolutePath()));
		}

		log.debug(HEADER + "[importReports]Import successful!");
		return reports;

	}

	private static File getPath(String path) throws FileNotFoundException {
		File filePath = new File(path);
		if (!filePath.exists()) {
			log.error(HEADER + "[checkPath]" + path + " doesn't exist!");
			throw new FileNotFoundException(path + " doesn't exist!");
		}
		return filePath;
	}

	private static void checkSamePath(File sourceFile, File backupFile) {
		if (sourceFile == null || backupFile == null) {
			log.error(HEADER + "[checkSamePath]Input parameters cann't be null.");
			throw new IllegalArgumentException("Input parameters cann't be null.");
		}

		if (sourceFile.getAbsolutePath().equals(backupFile.getAbsolutePath())) {
			log.error(HEADER + "[checkSamePath]The source path cann't be same as backup path.");
			throw new IllegalArgumentException("The source path cann't be same as backup path.");
		}
	}

	private static File[] getChildDirs(File rootFile) throws FileNotFoundException {
		File[] dirImports = rootFile.listFiles(new FileFilter() {
			@Override
			public boolean accept(File file) {
				return file.isDirectory() && (file.getName().startsWith("S") || file.getName().startsWith("A"));
			}
		});

		if (dirImports == null || dirImports.length < 1) {
			log.error(HEADER + "[getChildDirs]" + rootFile.getAbsolutePath() + " doesn't have the valid child dirs.");
			throw new FileNotFoundException(rootFile.getAbsolutePath() + " doesn't have the valid child dirs.");
		}
		return dirImports;
	}

	private static boolean checkBackupPath(File sourceFile, String backupParentPath) {
		File existFile = new File(backupParentPath + "/bak_" + sourceFile.getName());
		if (existFile.exists()) {
			log.debug(HEADER + "[checkBackupPath]The file " + existFile.getAbsolutePath() + " has existed!");
			return false;
		}
		return true;
	}

	private static File[] getReportFiles(File childDir) throws FileNotFoundException {
		File[] xmlFiles = childDir.listFiles(new FileFilter() {
			@Override
			public boolean accept(File file) {
				return file.isFile() && (file.getName().startsWith("S") || file.getName().startsWith("A"))
						&& file.getName().endsWith(".xml");
			}
		});

		if (xmlFiles == null || xmlFiles.length < 1) {
			log.error(HEADER + "[getReportFiles]" + childDir.getAbsolutePath() + " doesn't have the valid XML files.");
			throw new FileNotFoundException(childDir.getAbsolutePath() + " doesn't have the valid XML files.");
		}
		return xmlFiles;
	}

	private static void backupFile(File sourceFile, String backupParentPath) throws FileNotFoundException {
		if (sourceFile == null || !sourceFile.exists()) {
			log.error(HEADER + "[backupFile]The source file " + sourceFile.getAbsolutePath() + " doesn't exist.");
			throw new FileNotFoundException("The source file " + sourceFile.getAbsolutePath() + " doesn't exist.");
		}

		File file = new File(backupParentPath);
		if (!file.exists()) {
			log.debug(HEADER + "[backupFile]Create dir " + backupParentPath + ".");
			file.mkdirs();
		}

		sourceFile.renameTo(new File(backupParentPath + "/bak_" + sourceFile.getName()));
		log.debug(HEADER + "[backupFile]Backup to path " + backupParentPath + "/bak_" + sourceFile + ".");
	}

	private static void deleteDir(File dir) {
		File[] xmlFiles = dir.listFiles(new FileFilter() {
			@Override
			public boolean accept(File file) {
				return (file.getName().startsWith("S") || file.getName().startsWith("A")
						&& file.getName().endsWith(".xml"));
			}
		});

		if (xmlFiles.length == 0) {
			if (dir.listFiles().length > 0) {
				for (File child : dir.listFiles()) {
					log.debug(HEADER + "[deleteDir]Delete file " + child.getAbsoluteFile() + ".");
					child.delete();
				}
			}
			dir.delete();
			log.debug(HEADER + "[deleteDir]Delete dir " + dir.getAbsoluteFile() + ".");
		}
	}

}
